<!doctype html>
<html>
<head>
	<meta charset="UTF-8">
	<title>Magnifier Demo</title>
	<style type="text/css"> 
	body {
		margin: 0;
		padding: 0;
	}
	.container {
		width: 700px;
		height: 500px;
		margin: 100px auto;
	}
	.origin {
		float: left;
		position: relative;
		width: 300px;
		height: 300px;
		overflow: hidden;
		border: 1px solid #eee;
	}
	.origin .lens {
		position: absolute;
		top: 3px;
		left: 3px;		
		width: 50px;
		height: 50px;
		background: #666;
		z-index: 1;
		display: none;
		opacity: 0.3;
		filter: alpha(opacity: 30);
		border: 1px solid #000;
	}
	.origin .mask {
		width: 100%;
		height: 100%;
		top: 0;
		left: 0;
		position: absolute;
		z-index: 2;
		background: #000;
		cursor: move;
		opacity: 0;
		filter: alpha(opacity: 0);
	}
	.large {
		float: left;		
		width: 350px;
		height: 250px;
		padding: 2px;
		overflow: hidden;
		display: inline;
		position: relative;
		margin: 0 0 0 10px;
		display: none;
		border: 5px solid #eee;
		-webkit-box-shadow: #333 1px 1px 5px;
		-moz-box-shadow: #333 1px 1px 5px;
		box-shadow: #333 1px 1px 5px;
	}
	.large img {
		position: absolute;
		top: 0;
		left: 0;
	}
	</style>
</head>
<script type="text/javascript">

"use strict";

function $(id) {
	return document.getElementById(id);
}

function $$(oParent, elem) {
	return (oParent || document).getElementsByTagName(elem);
}

function $$$(oParent, className) {
	if (oParent.querySelectorAll) {
		return oParent.querySelectorAll('.' + className);
	} else {
		var els = $$(oParent, '*');
		var re = [];
		var i = 0;
		for (i = 0; i < els.length; i++) {
			if (els[i].className == className)
				re.push(els[i]);
		}
		return re;
	}

}

function Zoom() {
	this.init.apply(this, arguments);
}

Zoom.prototype = {
	init: function(options) {
		var _this = this;
		var config = {
			lensWidth: 50,
			lensHeight: 50
		}
		this.oContainer = $('magnifier');
		this.oLeft = $$$(this.oContainer, 'origin')[0];
		this.oLimg = $$(this.oLeft, 'img')[0];
		var zoom = this.oZoom = $$$(this.oContainer, 'large')[0];
		this.oRimg = $$(this.oZoom, 'img')[0];
		var mask = this.oMask = $$$(this.oContainer, 'mask')[0];
		var lens = this.oLens = $$$(this.oContainer, 'lens')[0];

		lens.style.width = (options && options.lensWidth || config.lensWidth) + 'px';
		lens.style.height = (options && options.lensHeight || config.lensHeight) + 'px';

		mask.onmouseover = function() {
			lens.style.display = 'block';
			zoom.style.display = 'block';
		};
		mask.onmouseout = function() {
			lens.style.display = 'none';
			zoom.style.display = 'none';
		};
		mask.onmousemove = function(e) {
			_this.mousemove(e);
		};
	},
	mousemove: function(e) {
		var ev = e || event;
		var lensX = (ev.clientX - this.oContainer.offsetLeft) - this.oLens.offsetWidth / 2;
		var lensY = (ev.clientY - this.oContainer.offsetTop) - this.oLens.offsetHeight / 2;
		var maxLeft = this.oMask.offsetWidth - this.oLens.offsetWidth;
		var maxTop = this.oMask.offsetHeight - this.oLens.offsetHeight;
		if (lensX < 0) {
			lensX = 0;
		} else if (lensX > maxLeft) {
			lensX = maxLeft;
		}
		if (lensY < 0) {
			lensY = 0;
		} else if (lensY > maxTop) {
			lensY = maxTop;
		}
		this.oLens.style.left = lensX + 'px';
		this.oLens.style.top = lensY + 'px';
		var percentX = lensX / maxLeft;
		var percentY = lensY / maxTop;
		this.oRimg.style.left = -percentX * (this.oRimg.offsetWidth - this.oZoom.offsetWidth) + 'px';
		this.oRimg.style.top = -percentY * (this.oRimg.offsetHeight - this.oZoom.offsetHeight) + 'px';
	}
};

window.onload = function() {

	new Zoom({
		lensWidth: 150,
		lensHeight: 150
	});

	// other way
	// new Zoom();
};

</script>
<body>
	<div class="container" id="magnifier">
		<div class="origin">
			<span class="lens"></span>
			<span class="mask"></span>
			<img src="http://images.cnitblog.com/blog/36987/201306/07000559-22f3428b42c94cbfb6c4e38361740d56.jpg" alt="origin image" />
		</div>
		<div class="large"><img src="http://images.cnitblog.com/blog/36987/201306/07000550-e9c81caad001460aaf9ed1871b18ea26.jpg" alt="large image" /></div>
	</div>
</body>
</html>